NeXT for Mac Devs
Volume Number: 6
Issue Number: 12
Column Tag: The Cross Developer
NeXT for Mac Programmers 
By C. Keith Ray, Irving, TX
NeXT programming for Mac Programmers
Object oriented programming is a hot topic in the press recently, but people in
the industry even now may not understand what all the excitement is about. I am a
Macintosh programmer who has lately been developing an application on the NeXT
cube, which is today the only machine for the mass market that requires programming
in an object-oriented language. (Of course, traditional text-based Unix programming
can be done in standard C.) And while it isn’t strictly required, NeXT strongly
encourages the use of Interface Builder, a kind of “resource editor” for linking
together the objects that comprise a NextStep-using application. Object-oriented
programming is, in its simplest explanation, a way of structuring code in a manner
somewhat different from the usual methods of structured programming. However, it
turns out that dynamic allocation of objects, polymorphism, and inheritance give
object-oriented programming a new kind of power that is hard for a traditional
programmer to imagine.
An object-oriented language, no matter how well designed, is not of immediate
benefit to its users unless a good object-library comes with it. The NextStep library
is written in NeXT Inc.’s version of Objective-C; it goes far beyond the minimal
library that come with commercial versions of Objective C for other computers. As a
very rough estimate, I would say that NextStep has all the functionality of MacApp plus
more features, but at a higher level of abstraction (with perhaps less freedom of
customization). Not having used MacApp (I’ve only read about it), I can not comment
further in this comparison.
The typical method of programming on the NeXT starts with Interface Builder.
Starting a new project, you are given a default window with resize, miniaturize, and
close controls, a default menu containing a few items, and a default panel for displaying
copyright information. Interface Builder has a palette containing selections for
additional defined and undefined menu items, panels and windows, and different kinds of
controls: buttons, sliders, scrolling-fields, text-fields, etc. You can create custom
versions of Interface Builder with additional palette objects. (Panels are windows that
would be used as modal or modeless dialogs.) A menu item brings up a an inspector
window, which can be used for managing the project’s files as well as textually
modifying selected objects. Using Interface Builder is fairly easy for any Mac
programmer already familiar with ResEdit, Prototyper, etc., though this program does
not have the most straight-forward user-interface. It can be rather frustrating at
first, and tedious as your skill grows.
Prototyper on the Macintosh allows linking buttons and menu items to dialogs and
windows, to provide a minimal amount of control -- opening or closing windows and
dialogs is about all you can do. Prototyper can also be used to generate an editable
resource file and C or Pascal code for handling dialogs, windows, scroll bars (with
some bugs in the version I used), menus, etc. You can then use that code as the
framework for your own programming, and you can rewrite the code as needed.
Interface Builder doesn’t work as a code generator in the same manner as Prototyper.
It creates a “.nib” file for your project, which seems to hold the data required for the
windows, menus, etc. No specifications for the format of the “.nib” have been
published as far as I know. (I suspect that Interface Builder takes advantage of
archiving methods implemented by all the AppKit classes.) During the link-step of
compiling to an executable, data from the “.nib” is put into a mach-file-segment.
Mach-file-segments may also hold the bitmap data from TIFF files to be used as icons
and pictures in and for the application. The code generated by IB only contains instance
variables that will refer to the objects you have used (menus, buttons, whatever),
methods to initialize those instance variables, and a main program stub that creates
the application-object, tells it to read in the data from the “.nib” segment, and starts
it running. You can also write code to dynamically load in .nib files, allowing multiple
instances of the same objects. In something almost approximating a SmallTalk
browser, you can have Interface Builder generate the Objective-C declarations in a
header file for a custom object class.
A major difference between Mac programs and NeXT programs is in the
event-handling structure. On the Mac, you have a top-level routine (often the main
program) that calls GetNextEvent or WaitNextEvent and branches through a switch or
case statement to decide on which routine should handle the most recent event according
to the current program state. On the NeXT, you normally create at least one custom
object, often a subclass of View, which you link via interface builder to the
user-interface objects. When you make the link, you specify what method the object
should call in your custom object. If your custom object has not already inherited a
definition for that method, then you have to write the code for that method. An example
is linking a button named “Launch Rockets” to your custom-view, calling the method
“rocketlaunch:sender”. Another example would be to link the menu item “Print” to
your custom view, calling the inherited method “PrintPSCode”. The way events reach
your code is kept behind the scenes: the application object gets events from the
event-queue in a manner similar to the Macintosh, it also knows which windows it has
and forwards appropriate events to those windows. The windows forward events to
whatever internal objects they know about, and so on through the hierarchy of views
and subviews of windows. Eventually an object receives an event that it knows how to
handle, and it calls a method to perform the appropriate action. The only code you
write are those methods to be called by the user-interface objects. The only time you
need to write code for checking events is when you are doing animation, or tracing
mouse movements in real time.
The source code example is an example of an Objective C program that could be
expanded into an arcade game. The main program merely gets the ball rolling, so to
speak -- the RocketView class is essentially the entire program. Note that the
program is completely passive, it only responds to events, and in this case the events
are the initial- window-exposed event, clicking in the launch-rockets button, and
choosing Print from the main menu. If you want your program to do something in the
absence of events, such as animating the missiles while waiting for other
button-presses, you will have to create timer- events to start up and/or continue your
animation-loop. The BreakApp example program that comes with the NeXT uses an
“Animator” object that simplifies creation of these timer- events, and can also be used
to check if a non-timer event has occurred.
Something that old-world (PC, mainframe) programmers may have a very
difficult time understanding, is that methods are not separate processes. (You can
write code C code to use multiple MACH threads, semaphores, etc., but that depends on
operating-system calls not related to Objective-C.) You generally cannot have a
method continuously executing and also have other methods respond to external events.
Nor are methods like interrupt-routines. You cannot have a method which will be
continued automatically after an another method interrupts it. It is possible to poll for
events in the Macintosh fashion, and go through a switch or case statement for handling
events, but then you can not use Interface Builder to link user-interface objects to call
methods in your code, and you lose the other benefit of having the
pseudo- resource-file that Interface Builder provides.
The compiler on the NeXT is the GNU C compiler, customized by NeXT to compile
Objective-C directly instead of using a preprocessor. The debugger is GNU’s symbolic
debugger “gdb”, which uses a command-line syntax and runs under the Shell. The
debugger is about as powerful as the THINK C and THINK Pascal symbolic debuggers,
though much more inconvenient. Because of the Free Software Foundation’s CopyLeft
agreement, you can obtain the source code of the compiler, the debugger, and EMACS,
with NeXT’s modifications, for $150 plus an magneto-optical disk.
All in all, the NeXT environment reflects the desire to provide a Macintosh-like
interface without duplicating the Macintosh’s difficulty in programming. The goal of
making NeXT programming easy to learn and powerful at the same time, has been met
with the NextStep object library and Interface Builder. The downside, just like Apple,
is that you have to follow the rules.
Next’s Application Kit, Sound Kit, and Music Kit, and Base Objective-C object
classes, in alphabetical order with inheritances listed -- all are ultimately descended
from Object.